﻿using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using TigerAndGoats.Sprites;

namespace TigerAndGoats.Framework
{
    public class ChequerGraph
    {
        private static ChequerGraph _currentChequerGraph;

        public string[] allPointsOrdinate = { 
            "2,-2"
                , "1,-1", "2,-1", "3,-1"
                ,"0,0", "1,0", "2,0", "3,0", "4,0"
                ,"0,1", "1,1", "2,1", "3,1", "4,1"
                ,"0,2", "1,2", "2,2", "3,2", "4,2"
                ,"0,3", "1,3", "2,3", "3,3", "4,3"
                ,"0,4", "1,4", "2,4", "3,4", "4,4"
        };

        public Dictionary<string, GraphNode> graphNodes = new Dictionary<string, GraphNode>();

        // 棋盘上的关键点
        private static Point _leftTopPoint = new Point(GlobalSettings.BORDER_WIDTH_X,
            GlobalSettings.BORDER_WIDTH_V + GlobalSettings.TITLE_HEIGHT + (GlobalSettings.VERTICAL_STEPS - GlobalSettings.HORIZONTAL_STEPS) * GlobalSettings.STEP_LENGTH);
        private static Point _rightTopPoint = new Point(GlobalSettings.BORDER_WIDTH_X + GlobalSettings.STEP_LENGTH * GlobalSettings.HORIZONTAL_STEPS,
            GlobalSettings.BORDER_WIDTH_V + GlobalSettings.TITLE_HEIGHT + (GlobalSettings.VERTICAL_STEPS - GlobalSettings.HORIZONTAL_STEPS) * GlobalSettings.STEP_LENGTH);
        private static Point _leftBottomPoint = new Point(_leftTopPoint.X, _leftTopPoint.Y + (GlobalSettings.HORIZONTAL_STEPS * GlobalSettings.STEP_LENGTH));
        private static Point _rightBottomPoint = new Point(_rightTopPoint.X, _rightTopPoint.Y + (GlobalSettings.HORIZONTAL_STEPS * GlobalSettings.STEP_LENGTH));

        private static Point _firstTigerPointTop = new Point((_leftTopPoint.X + _rightTopPoint.X) / 2, GlobalSettings.BORDER_WIDTH_V + GlobalSettings.TITLE_HEIGHT);
        private static Point _firstTigerPointLeft = new Point((_leftTopPoint.X + _firstTigerPointTop.X) / 2, GlobalSettings.BORDER_WIDTH_V + GlobalSettings.TITLE_HEIGHT
            + GlobalSettings.STEP_LENGTH);
        private static Point _firstTigerPointRight = new Point((_firstTigerPointTop.X + _rightTopPoint.X) / 2, GlobalSettings.BORDER_WIDTH_V + GlobalSettings.TITLE_HEIGHT
            + GlobalSettings.STEP_LENGTH);

        private static Action _refreshUI;
        public static void RefreshUI()
        {
            _refreshUI?.Invoke();
        }

        public ChequerGraph(Action refreshUI)
        {
            _refreshUI = refreshUI;
            InitGraphNodes();
        }

        public static ChequerGraph GetInstance(Action refreshUI = null)
        {
            if (_currentChequerGraph == null)
            {
                _currentChequerGraph = new ChequerGraph(refreshUI);
            }

            return _currentChequerGraph;
        }

        public void ChequerClickDetect(Point mouseLeftClickLocation)
        {
            string clickedOrdinate = GetClickedOrdinate(mouseLeftClickLocation);
            if (!string.IsNullOrEmpty(clickedOrdinate) && graphNodes.ContainsKey(clickedOrdinate))
            {
                var piece = graphNodes[clickedOrdinate].GetPiece();
                if (piece != Piece.Empty)
                {
                    if (!(piece is DestinationTip))
                    {
                        if (piece.IsPutup)
                        {
                            piece.PutDown();
                        }
                        else
                        {
                            piece.PutUp();
                        }
                    }
                    else
                    {
                        if (piece is DestinationTip)
                        {
                            var destination = piece as DestinationTip;
                            if (destination != null)
                            {
                                destination.WalkToHere();
                            }
                        }

                        if (piece is DestinationTipTiger)
                        {
                            var destination = piece as DestinationTipTiger;
                            if (destination != null)
                            {
                                destination.WalkToHere();
                            }
                        }
                    }
                }
            }
        }

        private string GetClickedOrdinate(Point mouseLeftClickLocation)
        {
            string x = RoundValueAtOneThird(mouseLeftClickLocation.X / (decimal)GlobalSettings.STEP_LENGTH);
            string y = RoundValueAtOneThird(mouseLeftClickLocation.Y / (decimal)GlobalSettings.STEP_LENGTH);
            if (x == string.Empty || y == string.Empty)
            {
                return string.Empty;
            }
            return $"{x},{y}";
        }

        private string RoundValueAtOneThird(decimal protoValue)
        {
            var baseValue = Math.Floor(protoValue);
            var leftValue = protoValue - baseValue;

            if (leftValue < (1/3m))
            {
                return (baseValue).ToString();
            }

            if (leftValue > (2/3m))
            {
                return (baseValue + 1).ToString();
            }

            return string.Empty;
        }

        public void DrawChequer(PaintEventArgs e)
        {
            // 创建棋盘
            var chequer = new System.Drawing.Drawing2D.GraphicsPath();
            // 初始化棋盘
            chequer.AddLine(_leftTopPoint, _rightTopPoint);
            chequer.AddLine(_rightTopPoint, _rightBottomPoint);
            chequer.AddLine(_rightBottomPoint, _leftBottomPoint);
            chequer.AddLine(_leftBottomPoint, _leftTopPoint);
            chequer.AddLine(_leftTopPoint, _rightBottomPoint);
            chequer.AddLine(_rightTopPoint, _leftBottomPoint);

            var middleLeftTopPoint1 = new Point(_leftTopPoint.X, (_leftTopPoint.Y + _leftBottomPoint.Y) / 2);
            var middleRightBottomPoint1 = new Point(_rightTopPoint.X, (_rightTopPoint.Y + _rightBottomPoint.Y) / 2);
            chequer.AddLine(middleLeftTopPoint1, middleRightBottomPoint1);

            // 绘制第一个老虎的老家
            chequer.AddLine(middleRightBottomPoint1, _firstTigerPointLeft);
            chequer.AddLine(_firstTigerPointLeft, _firstTigerPointTop);
            chequer.AddLine(_firstTigerPointTop, _firstTigerPointRight);
            chequer.AddLine(_firstTigerPointRight, middleLeftTopPoint1);

            var middleBottomPoint1 = new Point(_firstTigerPointTop.X, _leftBottomPoint.Y);

            chequer.AddLine(middleLeftTopPoint1, middleBottomPoint1);
            chequer.AddLine(middleBottomPoint1, middleRightBottomPoint1);

            // 绘制
            e.Graphics.DrawPath(Pens.Black, chequer);

            // 不能一笔画完的额外三条横线
            e.Graphics.DrawLine(Pens.Black, _firstTigerPointLeft, _firstTigerPointRight);
            int theTopY = (_leftTopPoint.Y + middleRightBottomPoint1.Y) / 2;
            e.Graphics.DrawLine(Pens.Black, new Point(_leftTopPoint.X, theTopY), new Point(_rightTopPoint.X, theTopY));
            int theBottomY = (_leftBottomPoint.Y + middleRightBottomPoint1.Y) / 2;
            e.Graphics.DrawLine(Pens.Black, new Point(_leftTopPoint.X, theBottomY), new Point(_rightTopPoint.X, theBottomY));
            // 不能一笔画完的额外三条竖线
            e.Graphics.DrawLine(Pens.Black, _firstTigerPointTop, middleBottomPoint1);
            int theLeftX = (_leftTopPoint.X + middleBottomPoint1.X) / 2;
            e.Graphics.DrawLine(Pens.Black, new Point(theLeftX, _leftTopPoint.Y), new Point(theLeftX, middleBottomPoint1.Y));
            int theRightX = (_rightTopPoint.X + middleBottomPoint1.X) / 2;
            e.Graphics.DrawLine(Pens.Black, new Point(theRightX, _rightTopPoint.Y), new Point(theRightX, middleBottomPoint1.Y));
        }

        public static Point GetLeftTopPoint()
        {
            return _leftTopPoint;
        }

        public static Point GetRightBottomPoint()
        {
            return _rightBottomPoint;
        }

        private void InitGraphNodes()
        {
            // First tiger top point
            graphNodes[allPointsOrdinate[0]] = new GraphNode(ordinate: allPointsOrdinate[0], (GraphNode gNode) =>
            {
                gNode.LeftTop = GraphNode.Empty;
                gNode.Top = GraphNode.Empty;
                gNode.RightTop = GraphNode.Empty;
                gNode.MiddleLeft = GraphNode.Empty;
                gNode.MiddleRight = GraphNode.Empty;
                gNode.BottomLeft = new GraphNode(this, ordinate: allPointsOrdinate[1], null);
                gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[2], null);
                gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[3], null);
            });

            // First tiger Bottom Left point
            graphNodes[allPointsOrdinate[1]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = GraphNode.Empty;
                    gNode.RightTop = graphNodes[allPointsOrdinate[0]];
                    gNode.MiddleLeft = GraphNode.Empty;
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[2]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[6], null);
                });

            // First tiger Bottom point
            graphNodes[allPointsOrdinate[2]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[0]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[1]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[3]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[6]];
                    gNode.BottomRight = GraphNode.Empty;
                });

            // First tiger Bottom Right point
            graphNodes[allPointsOrdinate[3]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[0]];
                    gNode.Top = GraphNode.Empty;
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[2]];
                    gNode.MiddleRight = GraphNode.Empty;
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[6]];
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = GraphNode.Empty;
                });
            // ------------------------------------------------------------------------------------
            // Main part point 6
            graphNodes[allPointsOrdinate[6]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[1]];
                    gNode.Top = graphNodes[allPointsOrdinate[2]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[3]];
                    gNode.MiddleLeft = new GraphNode(this, ordinate: allPointsOrdinate[5], null);
                    gNode.MiddleRight = new GraphNode(this, ordinate: allPointsOrdinate[7], null);
                    gNode.BottomLeft = new GraphNode(this, ordinate: allPointsOrdinate[10], null);
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[11], null);
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[12], null);
                });

            // Main part point 5,7,10,11,12
            // First tiger Bottom Right point
            graphNodes[allPointsOrdinate[5]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = GraphNode.Empty;
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = new GraphNode(this, ordinate: allPointsOrdinate[4], null);
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[6]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[10]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[7]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = GraphNode.Empty;
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[6]];
                    gNode.MiddleRight = new GraphNode(this, ordinate: allPointsOrdinate[8], null);
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[12]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[10]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[4]];
                    gNode.Top = graphNodes[allPointsOrdinate[5]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[6]];
                    gNode.MiddleLeft = new GraphNode(this, ordinate: allPointsOrdinate[9], null);
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[11]];
                    gNode.BottomLeft = new GraphNode(this, ordinate: allPointsOrdinate[14], null);
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[15], null);
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[16], null);
                });
            graphNodes[allPointsOrdinate[11]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[6]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[10]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[12]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[16]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[12]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[6]];
                    gNode.Top = graphNodes[allPointsOrdinate[7]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[8]];
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[11]];
                    gNode.MiddleRight = new GraphNode(this, ordinate: allPointsOrdinate[13], null);
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[16]];
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[17], null);
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[18], null);
                });

            // Main part point 4，8，9，14，15，16；13，17，18.
            graphNodes[allPointsOrdinate[4]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = GraphNode.Empty;
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = GraphNode.Empty;
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[5]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[9]];
                    gNode.BottomRight = graphNodes[allPointsOrdinate[10]];
                });
            graphNodes[allPointsOrdinate[8]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = GraphNode.Empty;
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[7]];
                    gNode.MiddleRight = GraphNode.Empty;
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[12]];
                    gNode.Bottom = graphNodes[allPointsOrdinate[13]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[9]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[4]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = GraphNode.Empty;
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[10]];
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[14]];
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[14]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[9]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[10]];
                    gNode.MiddleLeft = GraphNode.Empty;
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[15]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[19], null);
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[20], null);
                });
            graphNodes[allPointsOrdinate[15]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[10]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[14]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[16]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[20]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[16]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[10]];
                    gNode.Top = graphNodes[allPointsOrdinate[11]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[12]];
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[15]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[17]];
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[20]];
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[21], null);
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[22], null);
                });
            graphNodes[allPointsOrdinate[13]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[8]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[12]];
                    gNode.MiddleRight = GraphNode.Empty;
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[18]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[17]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[12]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[16]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[18]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[22]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[18]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[12]];
                    gNode.Top = graphNodes[allPointsOrdinate[13]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[17]];
                    gNode.MiddleRight = GraphNode.Empty;
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[22]];
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[23], null);
                    gNode.BottomRight = GraphNode.Empty;
                });

            // Main part point 19，20，21，22，23
            graphNodes[allPointsOrdinate[19]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[14]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = GraphNode.Empty;
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[20]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[24], null);
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[20]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[14]];
                    gNode.Top = graphNodes[allPointsOrdinate[15]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[16]];
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[19]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[21]];
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[24]];
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[25], null);
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[26], null);
                });
            graphNodes[allPointsOrdinate[21]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[16]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[20]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[22]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[26]];
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[22]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[16]];
                    gNode.Top = graphNodes[allPointsOrdinate[17]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[18]];
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[21]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[23]];
                    gNode.BottomLeft = graphNodes[allPointsOrdinate[26]];
                    gNode.Bottom = new GraphNode(this, ordinate: allPointsOrdinate[27], null);
                    gNode.BottomRight = new GraphNode(this, ordinate: allPointsOrdinate[28], null);
                });
            graphNodes[allPointsOrdinate[23]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[18]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[22]];
                    gNode.MiddleRight = GraphNode.Empty;
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = graphNodes[allPointsOrdinate[28]];
                    gNode.BottomRight = GraphNode.Empty;
                });

            // Main part point 24，25，26，27，28
            graphNodes[allPointsOrdinate[24]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[19]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[20]];
                    gNode.MiddleLeft = GraphNode.Empty;
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[25]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[25]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[20]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[24]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[26]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[26]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[20]];
                    gNode.Top = graphNodes[allPointsOrdinate[21]];
                    gNode.RightTop = graphNodes[allPointsOrdinate[22]];
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[25]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[27]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[27]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = GraphNode.Empty;
                    gNode.Top = graphNodes[allPointsOrdinate[22]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[26]];
                    gNode.MiddleRight = graphNodes[allPointsOrdinate[28]];
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = GraphNode.Empty;
                });
            graphNodes[allPointsOrdinate[28]].Initialize(
                (GraphNode gNode) =>
                {
                    gNode.LeftTop = graphNodes[allPointsOrdinate[22]];
                    gNode.Top = graphNodes[allPointsOrdinate[23]];
                    gNode.RightTop = GraphNode.Empty;
                    gNode.MiddleLeft = graphNodes[allPointsOrdinate[27]];
                    gNode.MiddleRight = GraphNode.Empty;
                    gNode.BottomLeft = GraphNode.Empty;
                    gNode.Bottom = GraphNode.Empty;
                    gNode.BottomRight = GraphNode.Empty;
                });
        }
    }
}
